﻿using HtmlAgilityPack;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;

namespace Business.Parsers {
    class Job51ResumeParser {
        public Resume Parse(string body) {
            var resume = new Resume();

            var doc = new HtmlDocument();
            doc.LoadHtml(body);

            // <span id="OLK_SRC_BODY_SECTION">中是原始邮件正文
            var resumeNode = doc.DocumentNode.SelectSingleNode("//span[@id='OLK_SRC_BODY_SECTION']");
            resume.HtmlBody = resumeNode.OuterHtml;
            

            // 情况概要，如：五年以上工作经验  |  男  |  32岁(1982年2月23日)  |  未婚
            var summary = resumeNode.SelectSingleNode("//td[text()='居住地：']").ParentNode.PreviousSibling.FirstChild.InnerHtml;
            resume.BirthYear = ParseBirthYear(summary);
            resume.Gender = ParseKeyWord(summary, new Dictionary<string, string> { { "男", "男" }, { "女", "女" } });
            resume.Marriage = ParseKeyWord(summary, new Dictionary<string, string> { { "已婚", "已婚" }, { "未婚", "未婚" } });
            resume.YearsOfWorking = ParseYearsOfWorkingExperience(summary);
            resume.HuKou = GetNextSiblingNodeText(resumeNode, "//td[text()='户　口：']");
            resume.Education = GetNextSiblingNodeText(resumeNode, "//td[text()='学　历：']");
            //resume.Major = GetNextSiblingNodeText(resumeNode, "//td[text()='专　业：']");

            // 姓名
            var nameNode = resumeNode.SelectSingleNode("//strong");
            if (nameNode != null)
                resume.Name = nameNode.InnerText;
            
            resume.PhoneNumber = GetNextSiblingNodeText(resumeNode, "//td[text()='电　话：']", "（手机）");
            resume.Position = GetNextSiblingNodeText(resumeNode, "//span[text()='应聘职位：']");
            // 期望月薪
            resume.Salary = ParseSalary(resumeNode);

            ParseRecentWork(resumeNode, resume);

            return resume;
        }

        private string ReplaceBlank(string s) {
            return Regex.Replace(s, @"\s+", string.Empty);
        }

        

        private void ParseRecentWork(HtmlNode resumeNode, Resume resume) {
            var lines = resumeNode.Single("//td[@class='cvtitle' and text()='工作经验']").NearestAncestor("table").FirstChild("table").Children("tr").ToArray();

            // hr标签分割了多个工作经历
            var workHistory = lines.Split((node) => node.FirstChild("hr").IsNotNull());

            foreach (var nodes in workHistory) {
                // 任职时间
                DateTime? from = null;
                DateTime? to = null;
                var timeNode = nodes[0].FirstChild("td");
                var matches = Regex.Matches(timeNode.InnerHtml, @"\d+\s*/\s*\d+", RegexOptions.IgnoreCase | RegexOptions.Singleline);
                if (matches.Count > 0)
                    from = DateTime.ParseExact(ReplaceBlank(matches[0].Value), "yyyy/M", CultureInfo.CurrentCulture);
                if (matches.Count > 1)
                    to = DateTime.ParseExact(ReplaceBlank(matches[1].Value), "yyyy/M", CultureInfo.CurrentCulture);

                // 任职信息
                string company = null;
                string position = null;
                position = nodes[2].Children("td").At(1).FirstChild("b").InnerHtml;
                var m = Regex.Match(timeNode.InnerHtml, @"：(.*)（", RegexOptions.IgnoreCase | RegexOptions.Singleline);
                if (m.Success)
                    company = m.Groups[1].Value;

                resume.AddWork(from, to, company, position);
            }
        }

        private int? ParseSalary(HtmlNode resumeNode) {
            var node = resumeNode.SelectSingleNode("//td[text()[normalize-space()='期望月薪：']]/span");
            var text = node.InnerHtml;
            var regex = new Regex(@"(\d+)\-\d+/月");
            var m = regex.Match(text);
            if (m.Success)
                return int.Parse(m.Groups[1].Value);
            throw new ArgumentException(text);
        }

        private string ParseKeyWord(string summary, IDictionary<string, string> keywords) {
            foreach (var kvp in keywords) {
                if (summary.Contains(kvp.Key))
                    return kvp.Value;
            }
            return null;
        }


        private int? ParseBirthYear(string summary) {
            var regex = new Regex(@"(\d{4})年");
            var m = regex.Match(summary);
            if (m.Success)
                return int.Parse(m.Groups[1].Value);
            return null;
        }

        private int? ParseYearsOfWorkingExperience(string summary) {
            var years = "一二三四五六七八九十";
            var regex = new Regex(@"(.{1})年以上工作经验");
            var m = regex.Match(summary);
            if (m.Success) {
                return years.IndexOf(m.Groups[1].Value) + 1;
            }
            return null;
        }

        private string GetNextSiblingNodeText(HtmlNode node, string xpath, string removeText = null) {
            var target = node.SelectSingleNode(xpath);
            if (target != null) {
                var next = target.NextSibling;
                // 如果本级节点找不到兄弟节点，尝试查找父节点的兄弟节点
                if (next == null)
                    next = target.ParentNode.NextSibling;
                if (next != null && next.InnerHtml != null) {
                    var text = next.InnerHtml;
                    if (!string.IsNullOrEmpty(removeText))
                        text = text.Replace(removeText, string.Empty);
                    return text;
                }
            }

            return null;
        }
    }
}
